# We attempt to identify a dense cluster of players in reputation space and
# track our own reputation to that. The idea is to trust the wisdom of the
# crowd and to be as inconspicuous as possible. We slack against those with
# reputations close to ours to eliminate competition.

import numpy as np

class Player:
    def __init__(self):
        self.n_hunt = 0
        self.n_slack = 0

    def hunt_choices(self, round_number, current_food, current_reputation, m,
                     player_reputations):
        if round_number == 1:
            # In the first round, hunt with all our partners.
            hunt_decisions = ['h' for rep in player_reputations]

        elif len(player_reputations) == 1:
            # Always slack against a single player.
            hunt_decisions = ['s']

        else:
            # Figure out how much we hunt this round.
            rsorted_reps = sorted(player_reputations, reverse=True)
            tmp = [rep for rep in rsorted_reps if rep != 0 and rep != 1]
            if len(tmp) > 0:
                rsorted_reps = tmp
            n_players = len(rsorted_reps) # number of players neither always
                                          # hunting nor always slacking
            n = int(np.ceil(np.sqrt(n_players))) # number of players to track
            n_widths = np.subtract(rsorted_reps[:n_players-(n-1)],
                                   rsorted_reps[n-1:])
            min_index = np.argmin(n_widths)
            max_index = min_index + n
            target_reps = rsorted_reps[min_index:max_index]
            target_rep = np.median(target_reps)
            target_n_hunt = int(round(target_rep * (self.n_hunt +
                                                    self.n_slack + n_players)))
            round_n_hunt = max(0, min(target_n_hunt - self.n_hunt, n_players))

            # Figure out who we hunt with.
            target_rep_diffs = np.absolute(np.subtract(player_reputations,
                                                       target_rep))
            hunt_indices = np.argsort(target_rep_diffs)[n_players -
                                                        round_n_hunt:]
            hunt_decisions = ['s' for rep in player_reputations]
            for index in hunt_indices:
                hunt_decisions[index] = 'h'

        # Bookkeeping.
        for decision in hunt_decisions:
            if decision == 'h':
                self.n_hunt += 1
            elif decision =='s':
                self.n_slack += 1

        return hunt_decisions

    def hunt_outcomes(self, food_earnings):
        pass

    def round_end(self, award, m, number_hunters):
        pass
